package com.shaozi.nc.manage;

import java.util.List;
import java.util.Map;
import java.util.Set;
import java.util.concurrent.ConcurrentHashMap;
import org.apache.log4j.Logger;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Lazy;
import org.springframework.stereotype.Component;
import org.springframework.util.StringUtils;
import com.shaozi.lib.concurrent.DefaultLocker;
import com.shaozi.lib.concurrent.Locker;
import com.shaozi.lib.manage.ManageBase;
import com.shaozi.nc.data.model.UserInfoModel;
import com.shaozi.nc.data.mongodao.CompanyUserInfoMDao;

/**
 * BeanUtils.getBean("companyUserInfoManage");
 * 
 * @author brenx
 * 
 */
@Component
@Lazy(true)
public class CompanyUserInfoManage extends ManageBase {
	private final Logger logger = Logger.getLogger(CompanyUserInfoManage.class);
	private Locker<String> locker = new DefaultLocker<>();

	/**
	 * compId =>uid==>UserInfoModel
	 */
	private Map<String, Map<String, UserInfoModel>> companyUserInfoMap;
	@Autowired
	private CompanyUserInfoMDao companyUserInfoMDao;

	public CompanyUserInfoManage() {
		companyUserInfoMap = new ConcurrentHashMap<String, Map<String, UserInfoModel>>();
	}

	public void delCacheByUser(String companyId, List<String> delIds) {
		if (delIds == null || delIds.size() < 1 || StringUtils.isEmpty(companyId)) {
			return;
		}
		for (String uid : delIds) {
			if (StringUtils.isEmpty(uid))
				return;
			Map<String, UserInfoModel> companyInfo = companyUserInfoMap.get(companyId);
			if (companyInfo != null) {
				companyInfo.remove(uid);
			}
		}
	}

	public void updateCacheByUser(String companyId, UserInfoModel userInfoModel) {
		if (userInfoModel == null || StringUtils.isEmpty(companyId)) {
			return;
		}
		Map<String, UserInfoModel> companyInfo = companyUserInfoMap.get(companyId);
		if (companyInfo != null) {
			companyInfo.put(userInfoModel.getUid(), userInfoModel);
		} else {
			companyInfo = new ConcurrentHashMap<String, UserInfoModel>();
			companyInfo.put(userInfoModel.getUid(), userInfoModel);
			companyUserInfoMap.put(companyId, companyInfo);
		}
	}

	public UserInfoModel getUserInfo(String companyId, String uid) {
		UserInfoModel userInfo = null;
		Map<String, UserInfoModel> companyInfo = getCompanyUserInfos(companyId);
		if (companyInfo != null) {
			userInfo = companyInfo.get(uid);
			if (userInfo == null) {
				userInfo = companyUserInfoMDao.getUserInfo(companyId, uid);
				if (userInfo != null) {
					companyInfo.put(userInfo.getUid(), userInfo);
				} else {

				}
			}
		} else {
			logger.debug("get company null:" + companyId);
		}
		return userInfo;
	}

	public Set<String> getCompanyIds() {
		return companyUserInfoMap.keySet();
	}

	public void updateUserInfo(String companyId, UserInfoModel userInfo) {
		if (userInfo == null)
			return;
		if (StringUtils.isEmpty(userInfo.getCompanyId()) || StringUtils.isEmpty(userInfo.getUid())
				|| StringUtils.isEmpty(userInfo.getUsername())) {
			return;
		}
		Map<String, UserInfoModel> companyInfo = companyUserInfoMap.get(companyId);
		if (companyInfo == null) {
			companyInfo = new ConcurrentHashMap<String, UserInfoModel>();
			companyUserInfoMap.put(companyId, companyInfo);
		}
		companyInfo.put(userInfo.getUid(), userInfo);
		companyUserInfoMDao.upsertUserBean(userInfo);
	}

	public void signUserInfoDeleted(String companyId, List<String> idList) {
		if (idList != null && idList.size() > 0) {
			delCacheByUser(companyId, idList);
			companyUserInfoMDao.signUserInfoDeleted(companyId, idList);
		}
	}

	public int getCompanyUserCount(String companyId) {
		Map<String, UserInfoModel> companyUsers = getCompanyUserInfos(companyId);
		if (companyUsers == null) {
			return 0;
		}
		return companyUsers.size();
	}

	public Map<String, UserInfoModel> getCompanyUserInfos(String companyId) {
		if (StringUtils.isEmpty(companyId))
			return null;
		locker.lock("CompanyUserInfoManage.getCompanyUserInfos" + companyId);
		try {
			Map<String, UserInfoModel> companyInfo = companyUserInfoMap.get(companyId);
			if (companyInfo == null) {
				List<UserInfoModel> userInfos = null;
				userInfos = companyUserInfoMDao.getCompanyUserInfos(companyId, UserInfoModel.USERINFO_EXIST);
				if (!userInfos.isEmpty()) {
					Map<String, UserInfoModel> companyUserInfos = new ConcurrentHashMap<String, UserInfoModel>();
					userInfos.forEach((user) -> {
						companyUserInfos.put(user.getUid(), user);
					});
					companyInfo = companyUserInfos;
					companyUserInfoMap.put(companyId, companyUserInfos);
				}
			}
			return companyInfo;
		} finally {
			locker.unlock("CompanyUserInfoManage.getCompanyUserInfos" + companyId);
		}
	}

	public void reloadCompanyUserInfo(String companyId) {
		locker.lock("CompanyUserInfoManage.getCompanyUserInfos" + companyId);
		try {
			List<UserInfoModel> userInfos = companyUserInfoMDao.getCompanyUserInfos(companyId,
					UserInfoModel.USERINFO_EXIST);
			if (!userInfos.isEmpty()) {
				Map<String, UserInfoModel> companyUserInfos = new ConcurrentHashMap<String, UserInfoModel>();
				userInfos.forEach((user) -> {
					companyUserInfos.put(user.getUid(), user);
				});
				companyUserInfoMap.put(companyId, companyUserInfos);
			}
		} finally {
			locker.unlock("CompanyUserInfoManage.getCompanyUserInfos" + companyId);
		}
	}

}
